#region Copyright(c) 2006 ZO, All right reserved.
// -----------------------------------------------------------------------------
// Copyright(c) 2006 ZO, All right reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are met:
//
//   1.  Redistribution of source code must retain the above copyright notice,
//       this list of conditions and the following disclaimer.
//   2.  Redistribution in binary form must reproduce the above copyright
//       notice, this list of conditions and the following disclaimer in the
//       documentation and/or other materials provided with the distribution.
//   3.  The name of the author may not be used to endorse or promote products
//       derived from this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
// WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
// EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
// OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
// WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
// OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
// ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// -----------------------------------------------------------------------------
#endregion


#region Using directives

using System.Collections;
using System.Windows.Forms.Design;
using ZO.SmartCore.Core;

#endregion

namespace ZO.SmartCore.Windows.Forms.Design
{
    /// <summary>
    /// Extends the design mode behavior of a Control. 
    /// </summary>
    public class SmartControlDesigner : ControlDesigner
    {

        #region Constructors

        /// <summary>
        /// Initializes a new instance of the <see cref="SmartControlDesigner"/> class.
        /// </summary>
        public SmartControlDesigner()
            : base()
        {
        }



        /// <summary>
        /// Initializes a new instance of the <see cref="SmartControlDesigner"/> class.
        /// </summary>
        /// <param name="propertiesToRemove">The properties to remove.</param>
        public SmartControlDesigner(string[] propertiesToRemove) : base()
        {
            this.propertiesToRemove = propertiesToRemove;
        }

        #endregion

        #region Destructor

        #endregion

        #region Fields
        private string[] propertiesToRemove;

        /// <summary>
        /// Track whether Dispose has been called.
        /// </summary>
        private DisposeState _disposeState = DisposeState.None;
        #endregion

        #region Events

        #endregion

        #region Operators

        #endregion

        #region Properties
        /// <summary>
        /// Get Whether Object is Disposed.
        /// </summary>
        /// <value>True If Object is disposed else false.</value>
        public bool IsDisposed
        {
            get { return (this._disposeState == DisposeState.Disposed); }

        }

        /// <summary>
        /// Get Whether Object is Disposing.
        /// </summary>
        /// <value>True If Object is Disposing.</value>
        public bool IsDisposing
        {
            get { return (this._disposeState == DisposeState.Disposing); }
        }

        #endregion

        #region Methods

        /// <summary>
        /// Removes the properties.
        /// </summary>
        /// <param name="properties">The properties.</param>
        private void RemoveProperties(IDictionary properties)
        {
            if (propertiesToRemove != null && properties != null)
            {
                foreach (string property in propertiesToRemove)
                {
                    if (properties.Contains(property))
                    {
                        properties.Remove(property);
                    }
                }
            }


        }

        /// <summary>
        /// Allows a designer to change or remove items from the set of properties that it exposes through a <see cref="T:System.ComponentModel.TypeDescriptor"></see>.
        /// </summary>
        /// <param name="properties">The properties for the class of the component.</param>
        protected override void PostFilterProperties(IDictionary properties)
        {
            RemoveProperties(properties);
            base.PostFilterProperties(properties);
        }


        /// <summary>
        /// Override This Method To Dispose Unmanaged Resources.
        /// </summary>
        protected virtual void DisposeManagedResources() { }

        /// <summary>
        /// Override This Method To Dispose Managed Resources.
        /// </summary>
        protected virtual void DisposeUnmanagedResources() { }


        /// <summary>
        /// Used Internally To Dipose Object.
        /// </summary>
        /// <param name="disposing">If true, this method is called because the object is being disposed with the Dispose() method. If false, the object is being disposed by the garbage collector.</param>
        protected override void Dispose(bool disposing)
        {
            //Check to see if Dispose has already been called.
            if ((this._disposeState != DisposeState.Disposed) & (this._disposeState != DisposeState.Disposing))
            {
                //change the state to Disposing
                this._disposeState = DisposeState.Disposing;

                try
                {
                    //If disposing equals true, dispose all managed 
                    // and unmanaged resources.
                    if (disposing)
                    {
                        this.DisposeManagedResources();
                        this.DisposeUnmanagedResources();

                    }
                    else
                    {
                        this.DisposeUnmanagedResources();
                    }

                }

                catch
                {
                    this._disposeState = DisposeState.None;
                    throw;
                }
                this._disposeState = DisposeState.Disposed;

                base.Dispose(disposing);

            }


        }

        #endregion
    }
}
